﻿// --------------------------------------------------------------------------------------------------------------------
// <copyright file="ThreeAndOneOrGateTest.cs" company="pwasiewicz">
//   pwasiewicz
// </copyright>
// <summary>
//   Defines the ThreeAndOneOrGateTest type.
// </summary>
// --------------------------------------------------------------------------------------------------------------------

namespace LogicSystem.Tests
{
    using System.Linq;

    using LogicSystem.Wires;

    using Microsoft.VisualStudio.TestTools.UnitTesting;

    /// <summary>The three and one or gate test.</summary>
    [TestClass]
    public class ThreeAndOneOrGateTest
    {
        /// <summary>
        /// Gets or sets the system simulator.
        /// </summary>
        /// <value>
        /// The system simulator.
        /// </value>
        public LogicSystemSimulator SystemSimulator { get; set; }

        /// <summary>
        /// Initializes this instance.
        /// </summary>
        [TestInitialize]
        public void Initialize()
        {
            var factory = new LogicElementsFactory();

            var wires = new Wire[9];
            for (var i = 0; i < 9; i++)
            {
                wires[i] = factory.CreateWire();
            }

            var and1 = factory.CreateGateAnd(wires[5], wires[0], wires[1]);
            var or1 = factory.CreateGateOr(wires[6], wires[2], wires[3]);
            var and2 = factory.CreateGateAnd(wires[7], wires[6], wires[4]);
            var and3 = factory.CreateGateAnd(wires[8], wires[5], wires[7]);

            wires[0].AddOutputGates(and1);
            wires[1].AddOutputGates(and1);

            wires[2].AddOutputGates(or1);
            wires[3].AddOutputGates(or1);

            wires[4].AddOutputGates(and2);
            wires[6].AddOutputGates(and2);

            wires[5].AddOutputGates(and3);
            wires[7].AddOutputGates(and3);

            this.SystemSimulator = factory.CreateLogicSystemSimulator(wires[8], wires.Take(5));
        }

        /// <summary>The simulating time test.</summary>
        [TestMethod]
        public void SimulatingTimeTest()
        {
            Assert.AreEqual(25, this.SystemSimulator.Simulate(Enumerable.Repeat(false, 5)));
        }

        /// <summary>Checks if output is true.</summary>
        [TestMethod]
        public void OutputTrueTest()
        {
            this.SystemSimulator.Simulate(true, true, false, true, true);
            Assert.AreEqual(true, this.SystemSimulator.OutputWire.State);
        }
    }
}
